use std::any::Any;
use std::collections::HashMap;
use std::sync::Arc;

use crate::core::beans::bean::{Bean, BeanManager};
use crate::core::beans::constants::{expansion_feature_names, expansion_seed_names};
use crate::core::manifest::{ActivationEventDefinition, ExpansionManifest};
use crate::core::services::context::ActivateContext;
use crate::core::services::context_manager::ContextManager;
use crate::core::services::contribution_keyword_manager::ContributionKeywordManager;
use crate::core::services::event_manager::EventManager;
use crate::core::services::extension_manager::ExtensionManager;
use crate::core::services::manifest_manager::ManifestManager;

/// `ExpansionSystem` 的配置选项
pub struct ExpansionSystemOptions {
    pub manifests: Vec<ExpansionManifest>,
    pub activation_event_definitions: Vec<ActivationEventDefinition>,
    // pub parent: Option<Arc<ExpansionSystem>> // 用于支持层级系统，暂不实现
}

/// 扩展系统主结构体
pub struct ExpansionSystem {
    id: String,
    bean_manager: Arc<BeanManager>,
}

impl ExpansionSystem {
    /// 创建一个新的扩展系统实例
    pub fn new(options: ExpansionSystemOptions) -> Arc<Self> {
        let mut seeds = HashMap::<&'static str, Arc<dyn Any + Send + Sync>>::new();
        seeds.insert(
            expansion_seed_names::MANIFESTS, 
            Arc::new(options.manifests)
        );
        seeds.insert(
            expansion_seed_names::ACTIVATION_EVENT_DEFINITIONS, 
            Arc::new(options.activation_event_definitions)
        );

        let bean_manager = Arc::new(BeanManager::new(seeds));

        let manifest_manager = ManifestManager::new(&bean_manager);
        bean_manager.add_bean(expansion_feature_names::MANIFEST_MANAGER, manifest_manager.clone());
        bean_manager.add_destructible(manifest_manager);

        let event_manager = EventManager::new(&bean_manager);
        bean_manager.add_bean(expansion_feature_names::EVENT_MANAGER, event_manager.clone());
        bean_manager.add_destructible(event_manager);

        let context_manager = ContextManager::new(&bean_manager);
        bean_manager.add_bean(expansion_feature_names::CONTEXT_MANAGER, context_manager.clone());
        bean_manager.add_destructible(context_manager);

        let contribution_manager = ContributionKeywordManager::new(&bean_manager);
        bean_manager.add_bean(expansion_feature_names::CONTRIBUTION_KEYWORD_MANAGER, contribution_manager.clone());
        bean_manager.add_destructible(contribution_manager);

        let extension_manager = ExtensionManager::new(&bean_manager);
        bean_manager.add_bean(expansion_feature_names::EXTENSION_MANAGER, extension_manager.clone());
        bean_manager.add_destructible(extension_manager);

        bean_manager.init();

        let system = Arc::new(Self {
            id: "root".to_string(),
            bean_manager: bean_manager.clone(),
        });

        let container = bean_manager.get_container();
        let mut beans = container.lock().unwrap();
        beans.insert(expansion_seed_names::EXPANSION_SYSTEM, system.clone());

        system
    }

    pub fn id(&self) -> &str {
        &self.id
    }

    pub fn destroy(&self) {
        self.bean_manager.destructor();
    }

    // --- 公共 API (委托给内部的管理器) ---

    pub async fn activate(&self, event_name: &str, repeat: bool) {
        let extension_manager = self.bean_manager
            .get_bean::<ExtensionManager>(expansion_feature_names::EXTENSION_MANAGER)
            .unwrap();
        extension_manager.activate(event_name, repeat).await;
    }

    pub async fn deactivate(&self, event_name: &str) {
        let extension_manager = self.bean_manager
            .get_bean::<ExtensionManager>(expansion_feature_names::EXTENSION_MANAGER)
            .unwrap();
        extension_manager.deactivate(event_name).await;
    }

    pub fn get_extension(&self, name: &str) -> Option<Arc<dyn Any + Send + Sync>> {
        let extension_manager = self.bean_manager
            .get_bean::<ExtensionManager>(expansion_feature_names::EXTENSION_MANAGER)
            .unwrap();
        extension_manager.get_api(name)
    }

    pub fn get_extension_context(&self, name: &str) -> Arc<ActivateContext> {
        let context_manager = self.bean_manager
            .get_bean::<ContextManager>(expansion_feature_names::CONTEXT_MANAGER)
            .unwrap();
        context_manager.get_activate_context(name)
    }

    pub async fn dynamic_add_manifest(&self, _manifests: Vec<ExpansionManifest>) {
        let _manifest_manager = self.bean_manager
            .get_bean::<ManifestManager>(expansion_feature_names::MANIFEST_MANAGER)
            .unwrap();
        // TODO: The underlying dynamic_add_manifest in ManifestManager needs to be async
        // manifest_manager.dynamic_add_manifest(manifests).await;
    }
}